grammar FishProtocol;


/*
格式

c1                                                                                                       无参数协议
c2{int=5,int=-1,int=0}                                                                                  3个参数协议
c3{int=5,string=6}                                                                                      2个参数协议
c4{int=5,string=6,float=0.3,double=0.6,bool=true,int[]=[1,2,3],object={"age":18,"name":"张三"}}          7个参数协议


c1
编译后:{"k":"c1","v":[]}

c2{int=5,int=-1,int=0}
编译后:{"k":"c2","v":[{"int":5},{"int":-1},{"int":0}]}

c3{int=5,string="6",float=0.3,double=0.6,bool=true,int[]=[1,2,3],net.User='{\"age\":18,\"name\":\"张三\"}'}
编译后:{"k":"c3","v":[{"int":5},{"string":6},{"float":0.3},{"double":0.6},{"bool":true},{"int[]":[1,2,3]},{"net.User":{"age":18,"name":"张三"}]}

帮我写一个g4文件实现如上格式的解析


c4{5,6l,0.3f,0.6,true}


c4{5,6l,0.3f,0.6D,"jjhgame8001","123456",true,null,[1,2,3],[1l,2l,3l],[0.1f,0.2f,0.3f],[0.1d,0.2d,0.3d],["a","b"],[true,false],net.User='{\"username\":\"jjhgame\",\"password\":\"123456\"}'}

c5{int=5,long=6l,float=0.3,double=0.6d,string="jjhgame8001",string="123456",bool=true,null,int[]=[1,2,3],long[]=[1l,2l,3l],float[]=[0.1f,0.2f,0.3f],double[]=[0.1d,0.2d,0.3d],string[]=["a","b"],bool[]=[true,false],net.User='{\"username\":\"jjhgame\",\"password\":\"123456\"}'}


//c4{5,6l,0.3f,0.6,true,"jjhgame","123456"}
//c4{5,6l,0.3f,0.6,true,'jjhgame','123456'}


*/

protocol
    : 'c' IntLiteral
    | 'c' IntLiteral params
    ;

params
    : '[' param (',' param)* ']'
    | '[' ']'
    | '{' param (',' param)* '}'
    | '{' '}'
    ;


param
    : IntLiteral                # IntLiteral
    | LongLiteral               # LongLiteral
    | FloatLiteral              # FloatLiteral
    | DoubleLiteral             # DoubleLiteral
    | StringLiteral             # StringLiteral
    | BooleanLiteral            # BooleanLiteral
    | NullLiteral               # NullLiteral
    | IntArr                    # IntArr
    | LongArr                   # LongArr
    | FloatArr                  # FloatArr
    | DoubleArr                 # DoubleArr
    | StringArr                 # StringArr
    | BoolArr                   # BoolArr

    | IntEQ                     # IntEQ
    | LongEQ                    # LongEQ
    | FloatEQ                   # FloatEQ
    | DoubleEQ                  # DoubleEQ
    | StringEQ                  # StringEQ
    | BoolEQ                    # BoolEQ
    | IntArrEQ                  # IntArrEQ
    | LongArrEQ                 # LongArrEQ
    | FloatArrEQ                # FloatArrEQ
    | DoubleArrEQ               # DoubleArrEQ
    | StringArrEQ               # StringArrEQ
    | BoolArrEQ                 # BoolArrEQ
    | NetObject                 # NetObject
    ;

IntEQ: 'int' '=' IntLiteral ;
LongEQ: 'long' '=' IntLiteral
    |'long' '=' LongLiteral ;
FloatEQ: 'float' '=' FloatLiteral ;
DoubleEQ: 'double' '=' FloatLiteral
    |'double' '=' DoubleLiteral ;
StringEQ: 'string' '=' StringLiteral
    |'string' '=' StringCharacters
    |'string' '=' SHORT_STRING;
BoolEQ: 'bool' '=' BooleanLiteral ;
IntArrEQ: 'int[]' '=' IntArr ;
LongArrEQ: 'long[]' '=' LongArr ;
FloatArrEQ: 'float[]' '=' FloatArr ;
DoubleArrEQ: 'double[]' '=' DoubleArr ;
StringArrEQ: 'string[]' '=' StringArr ;
BoolArrEQ: 'bool[]' '=' BoolArr ;

IntArr: '[' IntLiteral (',' IntLiteral)* ']';
LongArr: '[' LongLiteral (',' LongLiteral)* ']';
FloatArr: '[' FloatLiteral (',' FloatLiteral)* ']';
DoubleArr: '[' DoubleLiteral (',' DoubleLiteral)* ']';
StringArr: '[' StringLiteral (',' StringLiteral)* ']';
BoolArr: '[' BooleanLiteral (',' BooleanLiteral)* ']';

NetObject
    : 'net.' [a-zA-Z0-9$_]+ '=' SHORT_STRING
    ;


// §3.10.1 Integer Literals

IntLiteral
    :   [-]? DecimalNumeral
    |   [-]? HexNumeral
    |   [-]? OctalNumeral
    |   [-]? BinaryNumeral
    ;

LongLiteral
    :   [-]? DecimalIntegerLiteral
    |   [-]? HexIntegerLiteral
    |   [-]? OctalIntegerLiteral
    |   [-]? BinaryIntegerLiteral
    ;

fragment
DecimalIntegerLiteral
    :   DecimalNumeral IntegerTypeSuffix
    ;

fragment
HexIntegerLiteral
    :   HexNumeral IntegerTypeSuffix
    ;

fragment
OctalIntegerLiteral
    :   OctalNumeral IntegerTypeSuffix
    ;

fragment
BinaryIntegerLiteral
    :   BinaryNumeral IntegerTypeSuffix
    ;

fragment
IntegerTypeSuffix
    :   [lL]
    ;

fragment
DecimalNumeral
    :   '0'
    |   NonZeroDigit (Digits? | Underscores Digits)
    ;

fragment
Digits
    :   Digit (DigitOrUnderscore* Digit)?
    ;

fragment
Digit
    :   '0'
    |   NonZeroDigit
    ;

fragment
NonZeroDigit
    :   [1-9]
    ;

fragment
DigitOrUnderscore
    :   Digit
    |   '_'
    ;

fragment
Underscores
    :   '_'+
    ;

fragment
HexNumeral
    :   '0' [xX] HexDigits
    ;

fragment
HexDigits
    :   HexDigit (HexDigitOrUnderscore* HexDigit)?
    ;

fragment
HexDigit
    :   [0-9a-fA-F]
    ;

fragment
HexDigitOrUnderscore
    :   HexDigit
    |   '_'
    ;

fragment
OctalNumeral
    :   '0' Underscores? OctalDigits
    ;

fragment
OctalDigits
    :   OctalDigit (OctalDigitOrUnderscore* OctalDigit)?
    ;

fragment
OctalDigit
    :   [0-7]
    ;

fragment
OctalDigitOrUnderscore
    :   OctalDigit
    |   '_'
    ;

fragment
BinaryNumeral
    :   '0' [bB] BinaryDigits
    ;

fragment
BinaryDigits
    :   BinaryDigit (BinaryDigitOrUnderscore* BinaryDigit)?
    ;

fragment
BinaryDigit
    :   [01]
    ;

fragment
BinaryDigitOrUnderscore
    :   BinaryDigit
    |   '_'
    ;

// §3.10.2 Float  And Double Literals

FloatLiteral
    :   [-]? DecimalFloatingPointLiteral
    |   [-]? HexadecimalFloatingPointLiteral
    ;

fragment
DecimalFloatingPointLiteral
    :   Digits '.' Digits? ExponentPart? FloatTypeSuffix?
    |   '.' Digits ExponentPart? FloatTypeSuffix?
    |   Digits ExponentPart FloatTypeSuffix?
    |   Digits FloatTypeSuffix
    ;

fragment
HexadecimalFloatingPointLiteral
    :   HexSignificand BinaryExponent FloatTypeSuffix?
    ;

fragment
FloatTypeSuffix
    :   [fF]
    ;


//DoubleLiteral
DoubleLiteral
    :   [-]? DecimalDoubleLiteral
    |   [-]? HexadecimalDoubleLiteral
    ;

fragment
DecimalDoubleLiteral
    :   Digits '.' Digits? ExponentPart? DoubleTypeSuffix?
    |   '.' Digits ExponentPart? DoubleTypeSuffix?
    |   Digits ExponentPart DoubleTypeSuffix?
    |   Digits DoubleTypeSuffix
    ;

fragment
HexadecimalDoubleLiteral
    :   HexSignificand BinaryExponent DoubleTypeSuffix?
    ;

fragment
DoubleTypeSuffix
    :   [dD]
    ;

//float double 依赖

fragment
ExponentPart
    :   ExponentIndicator SignedInteger
    ;

fragment
ExponentIndicator
    :   [eE]
    ;

fragment
SignedInteger
    :   Sign? Digits
    ;

fragment
Sign
    :   [+-]
    ;






fragment
HexSignificand
    :   HexNumeral '.'?
    |   '0' [xX] HexDigits? '.' HexDigits
    ;

fragment
BinaryExponent
    :   BinaryExponentIndicator SignedInteger
    ;

fragment
BinaryExponentIndicator
    :   [pP]
    ;

// §3.10.3 Boolean Literals

BooleanLiteral
    :   'true'
    |   'false'
    ;

// §3.10.4 Character Literals

CharacterLiteral
    :   '\'' SingleCharacter '\''
    |   '\'' EscapeSequence '\''
    ;

fragment
SingleCharacter
    :   ~['\\]
    ;

// §3.10.5 String Literals

StringLiteral
    :   '"' StringCharacters? '"'
    |   '\'' StringCharacters? '\''
    ;

fragment
StringCharacters
    :   StringCharacter+
    ;

fragment
StringCharacter
    :   ~["\\]
    |   EscapeSequence
    ;

// §3.10.6 Escape Sequences for Character and String Literals

fragment
EscapeSequence
    :   '\\' [btnfr"'\\]
    |   OctalEscape
    |   UnicodeEscape
    ;

fragment
OctalEscape
    :   '\\' OctalDigit
    |   '\\' OctalDigit OctalDigit
    |   '\\' ZeroToThree OctalDigit OctalDigit
    ;

fragment
UnicodeEscape
    :   '\\' 'u' HexDigit HexDigit HexDigit HexDigit
    ;

fragment
ZeroToThree
    :   [0-3]
    ;

// §3.10.7 The Null Literal

NullLiteral
    :   'null'
    ;



//python str
fragment SHORT_STRING:
    '\'' (STRING_ESCAPE_SEQ | ~[\\\r\n\f'])* '\''
    | '"' ( STRING_ESCAPE_SEQ | ~[\\\r\n\f"])* '"'
;
fragment
STRING_ESCAPE_SEQ
    : '\\' .;
//    | '\\' NEWLINE;

//NEWLINE: ({this.atStartOfInput()}? SPACES | ( '\r'? '\n' | '\r' | '\f') SPACES?) {this.onNewLine();};
//fragment SPACES: [ \t]+;

